<template>
    <div>
      <div class="banner">
        <h1>vue原生轮播图</h1>
        <div class="item">
          <img :src="dataList[currentIndex]">
        </div>
        <!--图片列表要大于1-->
        <div class="page" v-if="this.dataList.length > 1">
          <ul>
            <li @click="gotoPage(prevIndex)">&lt</li>
            <!--点击圆点(类似a标签切换图片),循环遍历渲染三个圆点-->
            <li v-for="(item,index) in dataList" @click="gotoPage(index)"
                :class="{'current':currentIndex == index}">{{index+1}}</li>

            <li @click="gotoPage(nextIndex)">&gt</li>
          </ul>
        </div>
      </div>

      <h1>组件生命周期执行顺序见注释</h1>
      <div>{{testData}}</div>
    </div>
</template>

<script>
    export default {
        name: "VueLife",

        data(){
            return{
              dataList:["https://i1.mifile.cn/a4/xmad_15535933141925_ulkYv.jpg",
                "https://i1.mifile.cn/a4/xmad_15532384207972_iJXSx.jpg",
                "https://i1.mifile.cn/a4/xmad_15517939170939_oiXCK.jpg"],
              currentIndex: 0,   //默认显示图片
              timer: null ,   //定时器，
              xxx:{
                "xxx":"xxx"
              }
            }
        },
      computed: {
        //上一张
        prevIndex() {
          if(this.currentIndex == 0) {
            //...等于最后一张
            return this.dataList.length - 1;
          }else{
            return this.currentIndex - 1;
          }
        },
        //下一张
        nextIndex() {
          //...变成第一张
          if(this.currentIndex == this.dataList.length - 1) {
            return 0;
          }else {
            return this.currentIndex + 1;
          }
        },
        testData(){
          // 计算属性执行介于 beforeCreate 与  created 之间
          console.log("testData  computed")
          return  "testData"
        }
      },
      methods: {
        //计算属性作为实参
        gotoPage(index) {
          this.currentIndex = index;
        }
      },
      beforeCreate() {
        console.log("beforeCreate")
      },
      created() {
          //ajax请求最好放在created里面，因为此时已经可以访问this了，请求到数据就可以直接放在data里面。
          console.log('created')
      },
      /*computed计算属性 在 beforeMount前触发，计算属性的值在组件被缓存时 不会重复触发*/
      beforeMount() {
        console.log('beforeMount')
      },
      mounted(){
        //关于dom的操作要放在mounted里面，在mounted前面访问dom会是undefined。
        //定时器
        console.log('mounted')
        // this.timer = setInterval(() => {
        //   this.gotoPage(this.nextIndex)
        // }, 5000)
      },
      /*仅加了 keepAlive的 组件进入时会触发这个*/
      activated() {
        console.log('activated')
      },
      /*仅加了 keepAlive的 组件离开时会触发这个  且不会触发销毁*/
      deactivated() {
        console.log('deactivated')
      },
      /*数据更新前触发*/
      beforeUpdate() {
        console.log('beforeUpdate')
      },
      /*数据更新时触发*/
      updated() {
        console.log('updated')
      },
      /*页面销毁前触发*/
      beforeDestroy() {
        console.log('beforeDestroy')
      },
      /*页面销毁时触发*/
      destroyed() {
        console.log('destroyed')
      },
      watch: {
        /*在created之前和computed 之后执行*/
        $route: {
          /* 在create 之前执行  紧跟beforeCreate*/
          handler(to, from) {
            console.log("tofrom")
          },
          immediate: true,
          deep: true
        },
        /*watch 监听的计算属性 也是再计算属性之后执行*/
        testData:{
          immediate:true,
          handler(newVal,oldVal){
            console.log("watchtestData")
          }
        },
        /*在watchtestData 之后执行*/
        xxx: {
          /* 在create 之前执行  紧跟beforeCreate*/
          handler(newvalue,oldValue) {
            console.log("xxxValue")
          },
          immediate: true,
          deep: true
        },
      },

      // 仅限于该路由  这个不是写在这里的 在router里面写
/*      beforeEnter: (to, from, next) => {
      /!*    if (to.meta.isAuth) { //判断是否需要授权
          if (localStorage.getItem('school') === 'qinghuadaxue') {

          } else {
            alert('抱歉，您无权限查看！')
          }
        } else {
          next()  //放行
        }*!/
        console.log("beforeEnter")
        next()  //放行
      },

      beforeLeave: (to, from, next) => {
      /!*  if (to.meta.isAuth) { //判断是否需要授权
          if (localStorage.getItem('school') === 'qinghuadaxue') {
            next()  //放行
          } else {
            alert('抱歉，您无权限查看！')
          }
        } else {
          next()  //放行
        }*!/
        console.log("beforeLeave")
        next()
      },*/

      // 用路由规则进入该组件或离开该组件时，就会触发组件内守卫的调用，而组件内守卫的作用于范围也仅限于该组件
      // 执行 时机 在beforeCreated 之前执行
      beforeRouteEnter(to, from, next) {
        console.log("beforeRouteEnter")
        next(vm => {
          console.log("vm",vm)
          // 第三个参数next()，是否往下执行，执行的话，如果不写的话路由就不会跳转，操作将会终止
        });
      },
      beforeRouteUpdate(to, from, next) {
        console.log("beforeRouteUpdate")
        next(vm => {
          // 第三个参数next()，是否往下执行，执行的话，如果不写的话路由就不会跳转，操作将会终止
        });
      },
      // 执行 时机在beforeDestroy之前
      beforeRouteLeave(to, from, next) {
        console.log("beforeRouteLeave")
        next(vm => {
          // 第三个参数next()，是否往下执行，执行的话，如果不写的话路由就不会跳转，操作将会终止
        });
      },
    }
</script>

<style scoped>
  *{
    margin: 0;
    padding: 0;
  }
  ul li {
    list-style: none;
    float: left;
    width: 30px;
    height: 40px;
    line-height: 40px;
    text-align: center;
    cursor: pointer;
    color: rgba(255,255,255,.8);
    font-size: 14px;
  }
  .banner {
    max-width: 1200px;
    margin: 0 auto;
    position: relative;
    margin-top: 60px;
  }
  .banner img {
    width: 100%;
    display: block;
  }
  .banner .page {
    background: rgba(0,0,0,.5);
    position: absolute;
    right: 0;
    bottom: 0;
    width: 100%;
  }
  .banner .page ul {
    float: right;
  }
  .current {
    color: #ff6700;
  }

</style>

<!--
  beforeCreate
  testData  computed 计算属性
  watchtestData      watch监听的计算属性
  tofrom             wat监听的路由
  created
  beforeMount
  mounted
-->

<!--

触发钩子的完整顺序：

将路由导航、keep-alive、和组件生命周期钩子结合起来的，触发顺序，假设是从a组件离开，第一次进入b组件：

1- beforeRouteLeave:路由组件的组件离开路由前钩子，可取消路由离开。

2- beforeEach: 路由全局前置守卫，可用于登录验证、全局路由loading等。

3- beforeEnter: 路由独享守卫

4- beforeRouteEnter: 路由组件的组件进入路由前钩子。

5- beforeResolve:路由全局解析守卫

6- afterEach:路由全局后置钩子

7- beforeCreate:组件生命周期，不能访问this。

8- created:组件生命周期，可以访问this，不能访问dom。

9- beforeMount:组件生命周期

10- deactivated: 离开缓存组件a，或者触发a的beforeDestroy和destroyed组件销毁钩子。

11- mounted:访问/操作dom。

12- activated:进入缓存组件，进入a的嵌套子组件(如果有的话)。

13- 执行beforeRouteEnter回调函数next。


组件的加载渲染过程
　　父beforeCreate->父created->父beforeMount->子beforeCreate->子created->子beforeMount->子mounted->父mounted
子组件更新过程
　　父beforeUpdate->子beforeUpdate->子updated->父updated
父组件更新过程
　　父beforeUpdate->父updated
销毁过程
　　父beforeDestroy->子beforeDestroy->子destroyed->父destroyed

-->
